<?php


namespace App\Biquge;


use App\Job\Handler;
use App\Job\IJob;
use App\Job\QueueContract;
use App\Job\RedisJob;
use App\Job\RedisQueue;
use App\Utils\Cache;
use App\Utils\HttpUtil;
use App\Utils\Logger;
use Swoole\Server;

class NovalJobHandler implements Handler
{
    protected $queue = 'noval';

    protected $max_i = 5;
    protected $max_j = 5;

    protected $url = 'http://www.biqukan.com';

    public function onManagerStart(Server $server)
    {
        $server->redis = Cache::getRedis();
        $jobs = [];
        $old_i = $server->redis->get('MAX_I') ?? 0;
        $start_i = ($this->max_i - $old_i) > 0 ? $old_i : $this->max_i;

        $old_j = $server->redis->get('MAX_J') ?? 1;
        $start_j = ($this->max_j - $old_j) > 0 ? $old_j : $this->max_j;
        for ($i = $start_i; $i < $this->max_i; $i++) {
            for ($j = $start_j; $j < $this->max_j + 1; $j++) {
                $jobs[] = json_encode([
                    'job'=>  serialize(new NovalJob(sprintf('%s/%s_%s', $this->url, $i, ($i == 0 ? '' : $i) . $j))),
                    'attempts'=> 1
                ]);
            }
        }
//        $server->redis->set('MAX_I', $this->max_i);
//        $server->redis->set('MAX_J', $this->max_j);
        if ($jobs) {
            $server->redis->rpush($this->queue, $jobs);
        }
    }

    public function onManagerStop(Server $server)
    {
        unset($server->redis, $server->queue);
    }

    public function onWorkerStart(Server $server)
    {
        try {
            $server->queue = ioc(QueueContract::class);
            $server->request = new HttpUtil();
            Logger::getLogger('worker')->info("woker start");
            swoole_timer_tick(1000, function () use ($server) {
                if ($redisJob = $server->queue->dequeue($this->queue)) {
                    $server->task($redisJob);
                }
            });
        } catch (\Exception $e) {
            Logger::getLogger()->error($e);
            $server->shutdown();
        }
    }

    public function onTask(Server $server, RedisJob $redisJob)
    {
        try {
            $job = $redisJob->getJob();
            $job->handle();
            $redisJob->delete();
        } catch (\Exception $e) {
            dispatch($redisJob->getJob())->onQueue($redisJob->queue);
        }
    }

    public function dispatch()
    {
        while ($job = \ioc(RedisQueue::class)->dequeue('noval')) {
            preg_match('/http.*\d+/', print_r($job, true), $urls);
            dispatch(new NovalJob($urls[0]))->onQueue($this->queue);
        }
    }
}